home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Disc to the Future 2
/
Disc to the Future Part II Programmer's Reference (Wayzata Technology)(6013)(1992).bin
/
MAC
/
MPW_TOOL
/
TOOLS
/
TOOLS_WI
/
ICON_8
/
ICONX_FO
/
OCAT.C
< prev
next >
Wrap
Text File
|
1990-03-02
|
3KB
|
126 lines
/*
* File: ocat.c
* Contents: cat, lconcat
*/
#include "::h:config.h"
#include "::h:rt.h"
#include "rproto.h"
#ifdef PreProcess
/* include(../M4/ops.m4) /* */
/* */
#endif /* PreProcess */
/*
* x || y - concatenate strings x and y.
*/
OpDcl(cater,2,"||")
{
char sbuf1[MaxCvtLen]; /* buffers for conversion to string */
char sbuf2[MaxCvtLen];
/*
* Convert arguments to strings if necessary.
*/
if (cvstr(&Arg1, sbuf1) == CvtFail)
RunErr(103, &Arg1);
if (cvstr(&Arg2, sbuf2) == CvtFail)
RunErr(103, &Arg2);
if (StrLoc(Arg1) + StrLen(Arg1) == strfree) {
/*
* The end of Arg1 is at the end of the string space. Hence,
* Arg1 was the last string allocated. Arg1 is not copied.
* Instead, Arg2 is appended to the string space and the
* result is pointed to the start of Arg1.
* Space is only needed for the string being appended
*/
if (strreq(StrLen(Arg2)) == Error)
RunErr(0, NULL);
StrLoc(Arg0) = StrLoc(Arg1);
}
else {
/*
* Ensure space for the resulting concatenated string
*/
if (strreq(StrLen(Arg1) + StrLen(Arg2)) == Error)
RunErr(0, NULL);
/*
* Otherwise, append Arg1 to the end of the string space and
* point the result to the start of Arg1.
*/
StrLoc(Arg0) = alcstr(StrLoc(Arg1),StrLen(Arg1));
}
/*
* Append Arg2 to the end of the string space.
*/
alcstr(StrLoc(Arg2),StrLen(Arg2));
/*
* Set the length of the result and return.
*/
StrLen(Arg0) = StrLen(Arg1) + StrLen(Arg2);
Return;
}
/*
* x ||| y - concatenate lists x and y.
*/
OpDcl(lconcat,2,"|||")
{
register struct b_list *bp1, *bp2;
register struct b_lelem *lp1, *lp2;
word size1, size2;
/*
* x and y must be lists.
*/
if (Arg1.dword != D_List)
RunErr(108, &Arg1);
if (Arg2.dword != D_List)
RunErr(108, &Arg2);
/*
* Get the size of both lists.
*/
size1 = BlkLoc(Arg1)->list.size;
size2 = BlkLoc(Arg2)->list.size;
/*
* Make a copy of both lists.
*/
if (cplist(&Arg1, &Arg1, (word)1, size1 + 1) == Error)
RunErr(0, NULL);
if (cplist(&Arg2, &Arg2, (word)1, size2 + 1) == Error)
RunErr(0, NULL);
/*
* Get a pointer to both lists. bp1 points to the copy of Arg1 and is
* the list that will be returned.
*/
bp1 = (struct b_list *) BlkLoc(Arg1);
bp2 = (struct b_list *) BlkLoc(Arg2);
/*
* Perform the concatenation by hooking the lists together.
*/
lp1 = (struct b_lelem *) bp1->listtail;
lp2 = (struct b_lelem *) bp2->listhead;
lp1->listnext = (union block *) lp2;
lp2->listprev = (union block *) lp1;
/*
* Adjust the size field to reflect the length of the concatenated lists.
*/
bp1->size = size1 + size2;
bp1->listtail = bp2->listtail;
Arg0 = Arg1;
Return;
}